package com.example.demo.Servlet;

import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.AsyncContext;
import javax.servlet.AsyncEvent;
import javax.servlet.AsyncListener;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

/**
 * 使用Servlet方式进行异步请求
 */
@Slf4j
@RestController
public class ServletController {

    @RequestMapping(value = "/servlet/orig")
    public void todo(HttpServletRequest request, HttpServletResponse response) throws InterruptedException, IOException {
        response.setContentType("ext/html;charset=UTF-8");
        Thread.sleep(1000);
        response.getWriter().print("这是【正常】的请求返回");
    }

    @RequestMapping(value = "/servlet/async")
    public void todoAsync(HttpServletRequest request, HttpServletResponse response) {
        AsyncContext asyncContext = request.startAsync();
        asyncContext.addListener(new AsyncListener() {
            @Override
            public void onComplete(AsyncEvent asyncEvent) throws IOException {
                log.info("执行完成");
            }

            @Override
            public void onTimeout(AsyncEvent asyncEvent) throws IOException {
                log.info("超时了");
            }

            @Override
            public void onError(AsyncEvent asyncEvent) throws IOException {
                log.info("发生错误");
            }

            @Override
            public void onStartAsync(AsyncEvent asyncEvent) throws IOException {
                log.info("线程开始");
            }
        });
        asyncContext.setTimeout(20000);
        asyncContext.start(() -> {
            try {
                Thread.sleep(10000);
                System.out.println("ddddd");
                log.info("内部线程:"+Thread.currentThread().getName());
                asyncContext.getResponse().setCharacterEncoding("utf-8");
                asyncContext.getResponse().setContentType("text/html;charset=UTF-8");
                asyncContext.getResponse().getWriter().print("这是【异步】的请求返回");

            }catch (Exception e){
                log.error("异常",e);
            }
            //异步请求完成通知
            //此时整个请求才完成
            //其实可以利用此特性 进行多条消息的推送 把连接挂起。。
            asyncContext.complete();
        });
        System.out.println("main方法线程");
        //此时之类 request的线程连接已经释放了
        log.info("线程：" + Thread.currentThread().getName());
    }
}
